package com.zhongpengcheng.controller.common;

import com.zhongpengcheng.blog.auth.AuthToken;
import com.zhongpengcheng.blog.pojo.dto.ReauthorizationDTO;
import com.zhongpengcheng.blog.pojo.ro.LoginRO;
import com.zhongpengcheng.blog.pojo.po.LoginPO;
import com.zhongpengcheng.blog.util.ShiroUtils;
import com.zhongpengcheng.blog.util.TokenUtils;
import com.zhongpengcheng.blog.dao.pojo.db.UserDO;
import lombok.extern.slf4j.Slf4j;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.Assert;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;

/**
 * 鉴权相关接口，提供如下接口<br>
 * <ul>
 *     <li>登录，login</li>
 *     <li>登出，logout</li>
 *     <li>刷新token，reauthorize</li>
 * </ul>
 *
 * @author zhongpengcheng
 * @date 2021/08/13 16:25
 **/
@RestController
@RequestMapping("/auth")
@Slf4j
public class AuthController {

    /**
     * 登录
     */
    @PostMapping("/login")
    public LoginRO login(@RequestBody LoginPO po) {
        log.info("登录, req={}", po);
        SecurityUtils.getSubject().login(AuthToken.of(po.getUsername(), po.getPassword()));
        return LoginRO.builder()
                .accessToken(TokenUtils.createToken())
                .refreshToken(TokenUtils.createRefreshToken())
                .build();
    }

    /**
     * 登出
     */
    @PostMapping("/logout")
    public void logout(HttpServletRequest request) {
        // TODO: 实现实际登出逻辑
        String token = TokenUtils.getToken(request);
        UserDO user = ShiroUtils.getCurrentSysUser();
        Assert.notNull(token, "登出失败");
        log.info("{} logout, token={}", user.getUsername(), token);
    }

    /**
     * 刷新访问凭证
     */
    @PostMapping("/reauth")
    public ReauthorizationDTO refreshToken(HttpServletRequest request) {
        // TODO：实现实际token刷新逻辑
        String refreshToken = TokenUtils.getRefreshToken(request);
        Assert.notNull(refreshToken, "无效的Refresh Token");
        log.info("refresh token, refresh token={}", refreshToken);

        return TokenUtils.refreshToken(refreshToken);
    }
}
